﻿using System;

using Microsoft.Xna.Framework.Input;

using Storyteller.Framework.Graphics;

namespace Storyteller.Framework
{
	public abstract class Game : Microsoft.Xna.Framework.Game
	{
		internal static Game Instance { get; private set; }
		internal KeyboardState KeyboardState { get; private set; }
		internal MouseState MouseState { get; private set; }
		internal GamePadState[] GamePadStates { get; private set; }

		public int ScreenWidth { get; private set; }
		public int ScreenHeight { get; private set; }

		public Game(string windowTitle)
			: this(windowTitle, 1280, 720)
		{
		}

		public Game(string windowTitle, int screenWidth, int screenHeight)
		{
			if (Instance != null)
				throw new InvalidOperationException("Cannot instantiate multiple Xna.Game objects");

			Instance = this;

			new Microsoft.Xna.Framework.GraphicsDeviceManager(this)
			{
				PreferredBackBufferWidth = screenWidth,
				PreferredBackBufferHeight = screenHeight,
			};

			ScreenWidth = screenWidth;
			ScreenHeight = screenHeight;

			IsFixedTimeStep = false;
			IsMouseVisible = true;

			Window.Title = windowTitle;

			GamePadStates = new GamePadState[4];
		}

		public void Clear(Color color)
		{
			GraphicsDevice.Clear(new Microsoft.Xna.Framework.Color(color.R, color.G, color.B, color.A));
		}

		protected override void Update(Microsoft.Xna.Framework.GameTime gameTime)
		{
			KeyboardState = Keyboard.GetState();
			MouseState = Mouse.GetState();
			GamePadStates[0] = GamePad.GetState(Microsoft.Xna.Framework.PlayerIndex.One);
			GamePadStates[1] = GamePad.GetState(Microsoft.Xna.Framework.PlayerIndex.Two);
			GamePadStates[2] = GamePad.GetState(Microsoft.Xna.Framework.PlayerIndex.Three);
			GamePadStates[3] = GamePad.GetState(Microsoft.Xna.Framework.PlayerIndex.Four);

			base.Update(gameTime);
			Update((float)gameTime.ElapsedGameTime.TotalSeconds);
		}

		protected virtual void Update(float deltaSeconds)
		{
		}

		protected override void Draw(Microsoft.Xna.Framework.GameTime gameTime)
		{
			base.Draw(gameTime);
			Draw();
		}

		protected virtual void Draw()
		{
		}
	}
}
